package com.bigShen.spring;

/**
 * @author : lei.shen
 * @date : 2019/1/7
 */
public class HelloWorldSpring {


    public static void main(String[] args) {

    }

    public void chapter01() {
        /**
         *
         * Chapter1 : Spring 源码版本命名规则
         *   版本号格式 : X.Y.Z
         *   X : 主版本号  本次升级API兼容有变化, 需要升级主版本号, Y,Z重置为0
         *   Y : 次版本号  升级不影响兼容性变化, 比如新增接口,并不影响老的接口使用, 需要升级次版本号, Z重置为0
         *   Z : 修订号    有bug的修复时,递增的版本号
         *
         *    e.g : 5.1.3.RELEASE 表示5次大的改动主版本号升级,1次此版本号升级,3次bug修复,RELEASE 稳定版本;
         *      Snapshot: 版本代表不稳定、尚处于开发中的版本
         *      Alpha: 内部版本
         *      Beta: 测试版
         *      Demo: 演示版
         *      Enhance: 增强版
         *      Free: 自由版
         *      Full Version: 完整版，即正式版
         *      LTS: 长期维护版本
         *      Release: 发行版
         *      RC: 即将作为正式版发布
         *      Standard: 标准版
         *      Ultimate: 旗舰版
         *      Upgrade: 升级版
         *  Spring 版本命名规则
         *      1). Release 版本则代表稳定的版本
         *      2). GA 版本则代表广泛可用的稳定版(General Availability)
         *      3). M 版本则代表里程碑版(M 是 Milestone 的意思）具有一些全新的功能或是具有里程碑意义的版本。
         *      4). RC 版本即将作为正式版发布
         */
    }

    private void chapter02(){
        /**
         *
         * Spring源码研究可以从 spring-core入手, 之后看 spring-beans, spring-aop,
         * 之后 spring-context, 之后spring-tx,spring-orm, 最后是spring-web等其他组件;
         *
         * Spring大约20个模块, 主要可分为：
         *
         * 核心容器 : (beans, core, context, expression)
         *
         * AOP : (Aspect Oriented Programming)
         *
         * DB数据访问及集成 : (JDBC, ORM, JSM, OXM, Transaction)
         *
         * web : (webSocket, WebMVC, Web, WebFlux)
         *
         * 报文发送 : (Messaging)
         *
         * test : (test)
         *
         */

    }

    private void charpter03() {

        /**
         * 源码分析:
         * 1. IOC和DI
         *    我们一般创建对象都是通过一个java类来new出一个java对象,Spring是通过配置文件等配置好类class,
         *  然后交给IOC容器来创建对象, 也就是我们说的IOC控制反转;
         *    之后,Spring使用反射调用get,set方法来进行赋值, 称之为DI依赖注入;
         *
         * Spring IOC容器初始化:
         *  包括BeanDefinition的Resource的定位,载入,注册 三个步骤;
         *
         *
         * 2. 核心容器体系结构
         *  2.1)  Bean的管理  BeanFactory
         *      BeanFactory 是典型的工厂模式,有一系列的bean工厂:
         * BeanFactory是最顶层的接口,其下有三个子接口,
         *  org.springframework.beans.factory.HierarchicalBeanFactory            (存放有继承关系的Bean,也就是每个Bean有可能有父Bean)
         *  org.springframework.beans.factory.ListableBeanFactory                (存放可列表的Bean,)
         *  org.springframework.beans.factory.config.AutowireCapableBeanFactory （定义Bean的自动装配规则）
         * 这四个接口共同定义了Bean的集合,Bean之间的关系和Bean的行为;
         * 以上四个接口,最终的默认实现类为 org.springframework.beans.factory.support.DefaultListableBeanFactory;
         *
         *      BeanFactory接口只是定义了基本行为,并不关心具体的实现,Spring提供了许多具体的IOC容器实现,
         *  如 {@link org.springframework.beans.factory.xml.XmlBeanFactory}
         *  {@link org.springframework.context.support.ClassPathXmlApplicationContext}
         *  {@link org.springframework.context.ApplicationContext}
         *
         *  2.2) Bean的定义  BeanDefinition  org.springframework.beans.factory.support.RootBeanDefinition
         *  BeanFactory是Spring用来管理我们定义的各种Bean对象和其之间关系的;
         *  Bean在Spring具体实现中是以BeanDefinition描述的;
         *
         *  2.3) Bean的解析  XmlBeanDefinitionReader org.springframework.beans.factory.xml.XmlBeanDefinitionReader
         *  Bean的解析过程非常复杂,功能粒度备份的很细,主要的解析是针对Spring配置文件的解析;
         *  主要解析见: {@link org.springframework.beans.factory.xml.XmlBeanDefinitionReader}
         *
         *
         *
         *  3. IOC容器的初始化
         *  IOC容器初始化包括BeanDefinition的定位, 载入和注册三个过程;
         *  精简版: {@link org.springframework.beans.factory.xml.XmlBeanFactory}
         *
         * 以ApplicationContext容器为例, 我们常用的
         *    {@link org.springframework.context.support.ClassPathXmlApplicationContext}
         *    {@link org.springframework.context.support.FileSystemXmlApplicationContext }
         *    {@link org.springframework.web.context.support.XmlWebApplicationContext}
         *
         *    以FileSystemXmlApplicationContext为例解刨:
         *      3.1) 设置资源加载器和定位
         *
         *
         *
         *
         * 4. DI 依赖注入流程
         *  DI容器初始化:
         * 	默认在容器初始化时,解析资源配置文件至IOC容器后,如果bean配置的lazy-init为false时,直接进行初始化;
         * 	如果配置lazy-init为true时,当调用getBean()获取bean对象时,在进行对象初始化;
         * 	对象初始化可以分为两步:
         * 		1. 反射调用构造方法,生产bean的java对象实例,
         * 		2. 反射进行属性赋值,属性的依赖注入;
         *
         *      getBean :
         *   org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#createBean(java.lang.String, org.springframework.beans.factory.support.RootBeanDefinition, java.lang.Object[])
         * 		org.springframework.beans.factory.support.AbstractBeanFactory#doGetBean
         *
         * 			-- 构造方法创建对象
         * 			org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#createBeanInstance
         * 				org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#instantiateBean
         * 					org.springframework.beans.factory.support.SimpleInstantiationStrategy#instantiate(org.springframework.beans.factory.support.RootBeanDefinition, java.lang.String, org.springframework.beans.factory.BeanFactory)
         * 						(jdk & cglib 创建对象
         * 							(KotlinDetector.isKotlinReflectPresent() && KotlinDetector.isKotlinType(ctor.getDeclaringClass()) ?
         * 									KotlinDelegate.instantiateClass(ctor, args) : ctor.newInstance(args))
         * 							cglib : enhancedSubclassConstructor.newInstance(args)
         *
         * 						)
         *
         * 			org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#populateBean
         * 				org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#applyPropertyValues
         * 					org.springframework.beans.PropertyAccessor#setPropertyValues(org.springframework.beans.PropertyValues)
         * 						org.springframework.beans.AbstractNestablePropertyAccessor#setPropertyValue(org.springframework.beans.PropertyValue)
         * 							org.springframework.beans.AbstractNestablePropertyAccessor#setPropertyValue(org.springframework.beans.AbstractNestablePropertyAccessor.PropertyTokenHolder, org.springframework.beans.PropertyValue)
         * 								org.springframework.beans.AbstractNestablePropertyAccessor#processLocalProperty
         * 									org.springframework.beans.BeanWrapperImpl.BeanPropertyHandler#setValue
         * 										( jdk反射赋值
         * 										  writeMethod.invoke(getWrappedInstance(), value)
         * 										)
         */

    }


}
